package com.springsummer.information.green.webmvc;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.nio.charset.StandardCharsets;
import java.util.LinkedHashMap;
import java.util.Map;

public class SimpleHttpServer {

    public static void main(String[] args) throws Exception {
        int port = 8080;
        ServerSocket serverSocket = new ServerSocket(port);
        System.out.println("Server start listening on port " + port);

        while (true) {
            Socket clientSocket = serverSocket.accept();
            Runnable runnable=new Runnable() {
                @Override
                public void run() {
                    handleRequest(clientSocket);
                }
            };
            new Thread(runnable).start();
        }
    }

    private static void handleRequest(Socket clientSocket) {
        System.out.println("acceptConnection handleRequest clientSocket = " + clientSocket);
        try (BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()));
             OutputStream out = clientSocket.getOutputStream()) {

            String requestLine = in.readLine();
            if (requestLine == null) {
                System.out.println("clientSocket = " + clientSocket+" requestLine null");
                return;
            }
            System.out.println("requestLine = " + requestLine);

            String[] requestParts = requestLine.split(" ");
            if (requestParts.length < 3) {
                sendErrorResponse(out, 400, "Bad Request");
                return;
            }

            String method = requestParts[0];
            String url = requestParts[1];
            String httpVersion = requestParts[2];
            System.out.println("requestHeader method:" + method+" url:"+url+" httpversion:"+httpVersion);

            String parsedUrl = parseUrl(url);
            Map<String,String> parsedParams=parseQueryParamFromUrl(url);
            System.out.println("parsedUrl = " + parsedUrl);
            System.out.println("parsedParams = " + parsedParams);

            //String outBodyContent=parsedUrl;

            String outBodyContent=handleDispatch(parsedUrl);

            String htmlContent = "<html><body><h2 style=\"\n" +
                    "    color: blue;\n" +
                    "\"  >hello " + outBodyContent + "</h2></body></html>";
            byte[] htmlBytes = htmlContent.getBytes(StandardCharsets.UTF_8);

            String response = "HTTP/1.1 200 OK\r\n" +
                    "Content-Type: text/html; charset=utf-8\r\n" +
                    "Content-Length: " + htmlBytes.length + "\r\n" +
                    "\r\n";
            out.write(response.getBytes(StandardCharsets.UTF_8));
            out.write(htmlBytes);
            out.flush();

        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                clientSocket.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    //使用演示 http://localhost:8080/user/list?name=123
    public static String handleDispatch(String parsedUrl){
        ConnectionHandle connectionHandle=null;
        if(parsedUrl.contains("/user/add")){
            connectionHandle=new UserAddConnectionHandleImpl();
        }else if(parsedUrl.contains("/user/list")){
            connectionHandle=new UserListConnectionHandleImpl();
        }else{ //default
            connectionHandle=new UserListConnectionHandleImpl();
        }
        String handleResult= connectionHandle.handle(parsedUrl);
        String body=parsedUrl+" \r\n</br> "+handleResult+" ";
        return body;
    }

    private static String parseUrl(String url) {
        if (url.contains("?")) {
            String[] pathQuery = url.split("\\?", 2);

            return pathQuery[0];
        }
        return url;
    }

    private static Map<String, String> parseQueryParamFromUrl(String url) {
        if (url.contains("?")) {
            String[] pathQuery = url.split("\\?", 2);
            String queryParmStr = pathQuery[1];
            Map<String, String> params = parseQueryParam(queryParmStr);
            return params;
        }
        return new LinkedHashMap<>();
    }

    private static Map<String, String> parseQueryParam(String query) {
        Map<String, String> params = new LinkedHashMap<>();
        String[] pairs = query.split("&");
        for (String pair : pairs) {
            int idx = pair.indexOf("=");
            if (idx > 0) {
                String key = pair.substring(0, idx);
                String value = pair.substring(idx + 1);
                params.put(key, value);
            }
        }
        return params;
    }

    private static void sendErrorResponse(OutputStream out, int statusCode, String statusText) throws IOException {
        String response = "HTTP/1.1 " + statusCode + " " + statusText + "\r\n\r\n";
        out.write(response.getBytes(StandardCharsets.UTF_8));
        out.flush();
    }

}

